package com.ymt.bpm.service.remind;

import java.io.IOException;
import java.io.InputStream;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.Properties;
import java.util.UUID;

import javax.mail.Address;
import javax.mail.BodyPart;
import javax.mail.Message;
import javax.mail.Multipart;
import javax.mail.Session;
import javax.mail.Transport;
import javax.mail.internet.InternetAddress;
import javax.mail.internet.MimeBodyPart;
import javax.mail.internet.MimeMessage;
import javax.mail.internet.MimeMultipart;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.core.env.Environment;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;

import com.ymt.bpm.dao.remind.PMessageMapper;
import com.ymt.bpm.model.PMessage;
import com.ymt.bpm.model.PNotify;
import com.ymt.util.DateUtil;

@Service
public class SendMessageService {

	private Logger log = LoggerFactory.getLogger(this.getClass());
	
	private static Properties prop;

	@Autowired
	private Environment env;

	@Autowired
	private PMessageMapper mDao;

	private Session sendMailSession;
	private StringBuilder contentTemplate;
	private Address from;
	
	static {
		try {
			InputStream in = SendMessageService.class.getClassLoader()
					.getResourceAsStream("mail.properties");
			prop = new Properties();
			if(prop.isEmpty()){
				prop.load(in);
				in.close();
			}
		} catch(Exception e) {
			e.printStackTrace();
		}
	}
	
	public void notify(PNotify notify) throws Exception {
		switch(notify.getType()) {
			case "0":
				sendHtmlMail(notify);
				break;
			case "1":
				sendSms(notify);
				break;
			case "2":
				sendInsiteMessage(notify);
				break;
		}
	}
	
	/** 　  
　　　　 * 以HTML格式发送邮件
　　　　 * @param mailInfo 待发送的邮件信息
　　　　 */  
    public void sendHtmlMail(PNotify notify) throws Exception{
    	//首先，从配置文件读取发送邮件的配置信息
        Map<String, String> variables = new HashMap<String, String>();
        
        String title = this.getTitle(notify);
        String content = this.getContent(notify);
        
        //获取token的值
        variables.put("title", title);
        variables.put("sendtime", DateUtil.formatDate(new Date(), DateUtil.DATEFORMATSS_ZH, -480));	//TODO
        variables.put("receiver", notify.getReceiverName());
        variables.put("content", content);
        variables.put("read_url", notify.getReadUrl());
        variables.put("system_url", env.getProperty("mail.url-bpmp"));
       
        //get template
        if (contentTemplate==null) {
        	contentTemplate = new StringBuilder();
        	InputStream tin = SendMessageService.class.getClassLoader()
    				.getResourceAsStream("messageTemp.html");
            byte[] b = new byte[1024];
            int len = 0;
            while ((len = tin.read(b)) != -1) {  
            	contentTemplate.append(new String(b, 0, len, "utf-8"));  
            }
            //读完关闭字节流
            tin.close();
        }
        
        //为模板动态赋值
        String sendContent = contentTemplate.toString();	//每次重新由StringBuilder生成
        for (Map.Entry<String, String> variable : variables.entrySet()) {
        	sendContent = StringUtils.replace(sendContent, "{"+variable.getKey()+"}", variable.getValue());
        }
        
        //发送
        //从项目资源根目录下读取配置文件,也可以通过绝对路径来读取任意目录下的文件
		Properties defaultProps = new Properties();
		defaultProps.setProperty("mail.smtp.host", env.getProperty("mail.smtp-host"));
		defaultProps.setProperty("mail.transport.protocol", env.getProperty("mail.transport-protocol"));
		defaultProps.setProperty("mail.smtp.auth", env.getProperty("mail.smtp-auth"));
		defaultProps.setProperty("fromUser", env.getProperty("mail.fromUser"));
		defaultProps.setProperty("pwd", env.getProperty("mail.pwd"));
        if (sendMailSession==null) {
        	sendMailSession = Session.getDefaultInstance(defaultProps);
        	if (log.isTraceEnabled()) {
            	sendMailSession.setDebug(true);
            }
        }

        Message mailMessage = new MimeMessage(sendMailSession);
        if (from==null) {
        	from = new InternetAddress(env.getProperty("mail.fromUser"));
        }
        mailMessage.setFrom(from);
        Address to = new InternetAddress(notify.getDestination());
        mailMessage.setRecipient(Message.RecipientType.TO, to);
        mailMessage.setSubject(prop.getProperty( "tip.title") + title);
        mailMessage.setSentDate(new Date());
        //MiniMultipart类是一个容器类，包含MimeBodyPart类型的对象  
        Multipart mainPart = new MimeMultipart();
        //创建一个包含HTML内容的MimeBodyPart  
        BodyPart html = new MimeBodyPart();
        //设置HTML内容
        html.setContent(sendContent,"text/html; charset=utf-8");
        mainPart.addBodyPart(html);
        // 将MiniMultipart对象设置为邮件内容  
        mailMessage.setContent(mainPart);
        //发送邮件
        mailMessage.saveChanges();
        Transport transport = sendMailSession.getTransport("smtp");  
        transport.connect(env.getProperty("mail.smtp-host"),
				env.getProperty("mail.fromUser"),
				env.getProperty("mail.pwd"));
        transport.sendMessage(mailMessage, mailMessage.getAllRecipients());
        transport.close();
		if (log.isTraceEnabled()) {
			log.trace("mail sent ok.");
		}
    }
    
    public void sendSms(PNotify notify) throws IOException {
    	throw new RuntimeException("sms message is not implemented!");
    }
    
    public void sendInsiteMessage(PNotify notify) {
    	String title = this.getTitle(notify);
        String content = this.getContent(notify);
    	PMessage msg = new PMessage();
    	msg.setTenantId(notify.getTenantId());
    	msg.setMsgId("MSG-"+UUID.randomUUID().toString());
    	msg.setTitle(prop.getProperty("tip.title") + title);
    	msg.setContent(content);
    	msg.setReceiver(notify.getReceiver());
    	msg.setReceiverName(notify.getReceiverName());
    	msg.setSender(notify.getSender());
    	msg.setSenderName(notify.getSenderName());
    	msg.setSendTime(DateUtil.getGMTDate());
    	msg.setReadUrl(notify.getReadUrl());
    	msg.setStatus("0");
    	mDao.insert(msg);
    }
    
    private String getTitle(PNotify notify) {
    	StringBuilder title = new StringBuilder("");
    	if (notify.getTitle()!=null && notify.getTitle().length()>0) {
    		title.append(notify.getTitle());
		}
    	
    	if ("0".equals(notify.gettType())) {//新任务
    		title.append(prop.getProperty("tip.nttype.0.task"));
    	} else if ("1".equals(notify.gettType())) {
    		long now = DateUtil.getGMTDate().getTime();
        	long scheduled = notify.getScheduleTime().getTime();
        	long expired = notify.getExpireTime().getTime();
    		if (now>=scheduled && now < expired) {//任务逾期警告
    			title.append(prop.getProperty("tip.nttype.1.task.due"));
    		} else if (now >= expired) {//任务已逾期
    			title.append(prop.getProperty("tip.nttype.1.task.overdue"));
    		}
    	} else if ("2".equals(notify.gettType())) {//手动催办
    		title.append(notify.getSenderName());
    		title.append(prop.getProperty("tip.nttype.2.task.hasten"));
    	} else if ("3".equals(notify.gettType())) {
    		long now = DateUtil.getGMTDate().getTime();
        	long scheduled = notify.getScheduleTime().getTime();
        	long expired = notify.getExpireTime().getTime();
    		if (now>=scheduled && now < expired) {//流程逾期警告
    			title.append(prop.getProperty("tip.nttype.3.pi.due"));
    		} else if (now >= expired) {//流程已逾期
    			title.append(prop.getProperty("tip.nttype.3.pi.overdue"));
    		}
    	}
    	return title.toString();
    }
    
    private String getContent(PNotify notify) {
    	StringBuilder content = new StringBuilder("");
    	if ("0".equals(notify.gettType())) {//新任务
    		content.append(prop.getProperty("tip.content.nttype.0.task"));
    		content.append(getTodoSummary(notify));
    	} else if ("1".equals(notify.gettType())) {
    		long now = DateUtil.getGMTDate().getTime();
        	long scheduled = notify.getScheduleTime().getTime();
        	long expired = notify.getExpireTime().getTime();
    		if (now>=scheduled && now < expired) {//任务逾期警告
    			content.append(prop.getProperty("tip.content.nttype.1.task.due"));
    		} else if (now >= expired) {//任务已逾期
    			content.append(prop.getProperty("tip.content.nttype.1.task.overdue"));
    		}
    		content.append(getTodoSummary(notify));
    	} else if ("2".equals(notify.gettType())) {//手动催办
    		content.append(notify.getSenderName());
    		content.append(prop.getProperty("tip.content.nttype.2.task.hasten"));
    		content.append(getTodoSummary(notify));
    	} else if ("3".equals(notify.gettType())) {
    		long now = DateUtil.getGMTDate().getTime();
        	long scheduled = notify.getScheduleTime().getTime();
        	long expired = notify.getExpireTime().getTime();
    		if (now>=scheduled && now < expired) {//流程逾期警告
    			content.append(prop.getProperty("tip.content.nttype.3.pi.due"));
    		} else if (now >= expired) {//流程已逾期
    			content.append(prop.getProperty("tip.content.nttype.3.pi.overdue"));
    		}
    		content.append(getPiSummary(notify));
    	}
    	if (notify.getContent()!=null && notify.getContent().length()>0) {
    		content.append("<p>");
    		content.append(notify.getContent().replace(" ","&nbsp;"));
    		content.append("</p>");
    	}
    	String rtn = content.toString();
    	rtn = StringUtils.replace(rtn, 
    			"{expireTime}", 
    			DateUtil.formatDate(notify.getExpireTime(), DateUtil.DATEFORMATMM_ZH, -480));//TODO
    	return rtn;
    }
    
    private String getTodoSummary(PNotify notify) {
    	return "";
    }
    
    private String getPiSummary(PNotify notify) {
    	return "";
    }
    
    public static void main(String[] args) {
    	
	}
    
}
